home *** CD-ROM | disk | FTP | other *** search
/ Tech Arsenal 1 / Tech Arsenal (Arsenal Computer).ISO / tek-02 / htable.zip / GENTABLE.DOC < prev    next >
Text File  |  1993-01-04  |  9KB  |  189 lines

  1. (************************************************************************)
  2.  
  3.            Fully Generic, Fully Dynamic Hash Tables
  4.  
  5.            Author  : Eric C. Wentz
  6.            Phone   : 1-703-860-3807  (Before 11 P.M. Eastern)
  7.            C_Serve : 72070,1015
  8.  
  9.            UNIT REQUIREMENTS:  Requires Unit GENDATUM
  10.                                HTable.Arc Includes version 1.1
  11.                                of Unit GenDatum -- previously
  12.                                uploaded in GENERI.ARC -- soon to
  13.                                be uploaded in GENER2.ARC.
  14.                                (GenTable will work just fine
  15.                                with either version of GenDatum)
  16.                                Also requires the all-pervasive
  17.                                Unit FLEXPNTR -- found in unit
  18.                                GENERI.ARC (GenDatum needs it)
  19.                                You're right -- shameless of me
  20.                                to force you to download another
  21.                                of my uploads!
  22.  
  23.            For all you "OverLay Cowboys" out there, GenTable IS
  24.            compiled in the O+ state.
  25.  
  26. (************************************************************************)
  27.  
  28. { Unit GenTable  written by Eric C. Wentz -- last mod Date: 12/15/89 }
  29.  
  30. { Implements a String-keyed Hash Table of Generic Datum Objects }
  31.  
  32. { See Unit GenDatum }
  33.  
  34. { The Hash Tables defined herein use the External Chaining solution for  }
  35. { hashing. The Hashing Function used IS case-sensitive.                  }
  36.  
  37. { Data to be entered into the Hash Table is loaded into a Generic Object }
  38. { (EntryRec) and then the EntryRec is Inserted/Appended into the Hash    }
  39. { Table location determined by the Key string associated with the entry. }
  40. { Retrieval is accomplished by a similar, albeit reversed, process --    }
  41. { with the obvious exception that the entry is not deleted.  Keys may be }
  42. { examined for Membership in the Hash Table, or a boolean Found may be   }
  43. { returned by Retrieve.  Duplicate Keys will not be inserted, and are    }
  44. { flagged by Enter's boolean variable Duplicate.                         }
  45.  
  46.  
  47. (**** Simulated Interface -- Private declarations removed ****
  48.  
  49. Type
  50.   KeyString = String[20];  { Maximum Key Length }
  51.  
  52.   HTable = Object
  53.  
  54.           Constructor Create (LoadFactor,DataSize : Word;
  55.                                         MaxEntries : LongInt);
  56.  
  57.              { CREATE: LoadFactor represents the Number of entries the    }
  58.              { caller would LIKE to see in each "Bucket" of the final     }
  59.              { Hash Table.  Probably only achievable if you provide a     }
  60.              { PERFECT Hashing function for your Keys and Table.          }
  61.              { DataSize is the SizeOf the Elements you wish to Hash.      }
  62.              { MaxEntries is the Max Number of Table Entries you expect   }
  63.              { to need -- It does NOT actually limit the size of the      }
  64.              { Table!  The Table uses MaxEntries, DataSize and LoadFactor }
  65.              { to determine the number of "Buckets" to allocate.  HTables }
  66.              { can grow to the point of using all available Heap Space    }
  67.              { (althought this is VERY unlikely due to hidden factors),   }
  68.              { but the more "Buckets there are the better performance you }
  69.              { will get.  If Memory is no Object (oops!) (sorry), simply  }
  70.              { use 0 for both LoadFactor and MaxEntries.  This will cause }
  71.              { the Table to use as many "Buckets" as it can cram into RAM }
  72.  
  73.           Destructor Destroy; Virtual;
  74.  
  75.              { DESTROY: This routine returns ALL memory used by the Table }
  76.              { to the Heap.  For Large Tables, Destroy can take a VERY    }
  77.              { long time.  Fear Not, Destroy Can't lock-up your machine,  }
  78.              { even though you may well begin to think it has!!!          }
  79.  
  80.           Procedure Enter (TheKey : String; Var D; D_Size : Word;
  81.                                             Var Duplicate : Boolean);
  82.  
  83.              { ENTER: TheKey is the Key to be associated with the data in }
  84.              { the Typeless parameter D.  D_Size is the SizeOf D.         }
  85.              { Duplicate is the indication that a duplicate key has been  }
  86.              { encountered.  Duplicate Keys cause the table to refuse to  }
  87.              { accept the data.                                           }
  88.  
  89.           Procedure Retrieve (TheKey : String; Var D; D_Size : Word;
  90.                                          Var Found : Boolean);
  91.  
  92.              { RETRIEVE: TheKey is the Key to be searched for.  If NOT    }
  93.              { Found, D will contain whatever it initially had, else it   }
  94.              { will contain the data previously associated with TheKey.   }
  95.              { D_Size is the size of that data element.                   }
  96.  
  97.           Procedure UpDate (TheKey : String; Var D; D_Size : Word);
  98.  
  99.              { UPDATE: Permits the Data associated with Key to be updated }
  100.              { to that contained in D.                                    }
  101.  
  102.           Function Hash (TheString : String) : Word; Virtual;
  103.  
  104.              { HASH: MUST return a number in range 0..StaticLength-1 }
  105.  
  106.           Function Member (TheKey : String) : Boolean;
  107.  
  108.              { MEMBER: Is Key in the Table? }
  109.  
  110.           Function Empty          : Boolean;
  111.  
  112.              { EMPTY: Is the Table Empty? }
  113.  
  114.  
  115. { The Following routines are provided to aid in more effective Hash function }
  116. { design, as well as provide statistics about the utilization of a given     }
  117. { Table - to aid in choosing LoadFactor and MaxEntries for final application }
  118. { programs.  They provide little that is useful beyond the development stage.}
  119.  
  120.           Function StaticLength : Word;
  121.  
  122.              { STATICLENGTH: The number of "Buckets" in this Table }
  123.  
  124.           Function EntryCount     : Word;
  125.  
  126.              { ENTRYCOUNT: How many entries are in the Table? }
  127.  
  128.           Function MaxLoad        : Byte;
  129.  
  130.              { MAXLOAD: How many entries are in the "largest Bucket" ? }
  131.  
  132.           Function Buckets_In_Use : Word;
  133.  
  134.              { BUCKETS_IN_USE: How many Buckets are ACTUALLY being used? }
  135.  
  136.           Function AverageLoad    : Real;
  137.  
  138.              { AVERAGELOAD: What is the Average Load for those "Buckets" }
  139.              {              which are currently being used?              }
  140.  
  141.           Function LastBucket     : Word;
  142.  
  143.              { LASTBUCKET: What is the index of the last active "Bucket" ? }
  144.  
  145.           Procedure Distribution_Report;
  146.  
  147.              { DISTRIBUTION_REPORT: Print to screen certain statistics }
  148.              {                      regarding "Bucket" utilization.    }
  149.  
  150.         End;
  151.  
  152. **** End of simulated Interface ****)
  153.  
  154. The HTable Object can be visualized as a FlexArray (see GENERI.ARC) of
  155. pointers to linked lists of records.  Each pointer represents a "Bucket",
  156. and each list represents the contents of that bucket.  Internally, while
  157. similar to the FlexArray, FlexArrays are not actually used (for code
  158. optimization) so none of the familiar FlexArray features are available, such
  159. as ReSize.  Thus, once Created, each HTable has a certain fixed number of
  160. buckets associated with it.  This fixed number is either determined by the
  161. user (in the call to Create) as MaxEntries Div LoadFactor, or will be
  162. determined by Create if the user opts for 0,0.  If the user selects 0,0
  163. Create will allocate as many buckets as available memory will permit
  164. (using the size of the internal record as size criterion).  For this
  165. reason, I do not recommend the 0,0 option except in the most unusual
  166. circumstances.  Remember, MaxEntries does not limit the entrie the table
  167. can accept - only available memory does that - MaxEntries is simply a
  168. device for attempting to achieve the desired LoadFactor, which of course
  169. directly relates to HTable retrieval performance.  KeyStrings are internally
  170. limited to 20 characters simply to keep the size of these internal records
  171. reasonable -- in practice String[255] worked just as well, but caused the
  172. tables to gobble huge hunks of memory.  Since there may be some good use
  173. for such huge Hash keys, I have included Unit GenTabl2 which is EXACTLY
  174. the same as GenTable, but compiled with the Maximum Key length of 255.
  175. BE WARNED: GenTabl2 is a MEMORY HOG!
  176.  
  177. The Source code included with HTABLE.ARC is granted to the public domain.
  178. The source code for GenDatum and GenTable (and GenTable2) is neither
  179. included, nor granted to the public domain, but the use of the compiled
  180. units most certainly is!
  181.  
  182. Comments, suggestions, complaints and questions should be sent to
  183. my compuserve account (listed above), or feel free to call me
  184. (at a reasonable hour, please!).  I am especially interested in any
  185. bugs which I may have overlooked.  While I have tested these units as
  186. much as I can conceive, I have found that testing is an art form in and
  187. of itself, and I have not yet mastered its every little intricacy.
  188.  
  189. Enjoy!